Popular Searches
Popular Course Categories
Popular Courses

Working with Lists in Dart

Working with Lists in Dart

Flutter Lists & Collections

Working with Lists in Dart

Lists are one of the most commonly used collection types in Dart. A List stores multiple values in an ordered sequence, and each value can be accessed using an index. Lists are especially important in Flutter because they are frequently used to manage UI data such as products, users, messages, categories, menu items, and API responses.

In Dart, a list is an indexable collection of objects. List indexes start from 0, so the first element is at index 0 and the last element is at length - 1.

1. What is a List?

A List is an ordered collection of values. Unlike a Set, a List preserves the order of its elements and allows duplicate values.

List fruits = ['Apple', 'Banana', 'Mango'];
print(fruits);

Output:

[Apple, Banana, Mango]

Important Characteristics

  • Lists are ordered collections.
  • List indexing starts from 0.
  • Lists can contain duplicate values.
  • Lists can be growable or fixed-length.
  • Lists can be strongly typed using generics.
  • Lists provide many useful methods for adding, removing, searching, sorting, and transforming data.

2. Creating a List

Using a List Literal

var numbers = [10, 20, 30, 40, 50];

Dart can infer the list type from its values, so the above list is inferred as List.

Creating an Explicitly Typed List

List names = ['Amit', 'Rahul', 'Neha'];
List marks = [80, 75, 92];
List prices = [99.99, 149.50, 299.00];

Creating an Empty List

List students = [];
students.add('Rahul');
students.add('Priya');
print(students);

Using Generic Type Syntax

var cities = ['Mumbai', 'Delhi', 'Pune'];

3. Accessing List Elements

Use square brackets [] with an index to access an element.

List fruits = ['Apple', 'Banana', 'Mango'];

print(fruits[0]);
print(fruits[1]);
print(fruits[2]);

Output:

Apple
Banana
Mango

Index Positions

IndexValue
0Apple
1Banana
2Mango

4. Getting the Length of a List

The length property returns the number of elements in a list.

var numbers = [10, 20, 30, 40];

print(numbers.length);

Output:

4

5. Updating List Elements

List elements can be changed using their indexes.

var fruits = ['Apple', 'Banana', 'Mango'];

fruits[1] = 'Orange';

print(fruits);

Output:

[Apple, Orange, Mango]

6. Checking Whether a List is Empty

Dart provides isEmpty and isNotEmpty properties.

var items = [];

print(items.isEmpty);
print(items.isNotEmpty);

Output:

true
false

7. Adding Elements to a List

Using add()

The add() method adds one element to the end of a growable list.

var fruits = ['Apple', 'Banana'];

fruits.add('Mango');

print(fruits);

Output:

[Apple, Banana, Mango]

Using addAll()

The addAll() method adds multiple elements.

var fruits = ['Apple', 'Banana'];

fruits.addAll(['Mango', 'Orange', 'Grapes']);

print(fruits);

Output:

[Apple, Banana, Mango, Orange, Grapes]

8. Inserting Elements

Using insert()

The insert() method adds an element at a specific index.

var fruits = ['Apple', 'Mango'];

fruits.insert(1, 'Banana');

print(fruits);

Output:

[Apple, Banana, Mango]

Using insertAll()

var numbers = [10, 50];

numbers.insertAll(1, [20, 30, 40]);

print(numbers);

Output:

[10, 20, 30, 40, 50]

9. Removing Elements

remove()

Removes the first matching element.

var fruits = ['Apple', 'Banana', 'Mango'];

fruits.remove('Banana');

print(fruits);

removeAt()

Removes an element at a specific index.

var fruits = ['Apple', 'Banana', 'Mango'];

fruits.removeAt(1);

print(fruits);

Output:

[Apple, Mango]

removeLast()

var numbers = [10, 20, 30];

numbers.removeLast();

print(numbers);

removeRange()

var numbers = [10, 20, 30, 40, 50];

numbers.removeRange(1, 4);

print(numbers);

Output:

[10, 50]

clear()

The clear() method removes all elements.

var fruits = ['Apple', 'Banana', 'Mango'];

fruits.clear();

print(fruits);

Output:

[]

10. Searching in a List

contains()

var fruits = ['Apple', 'Banana', 'Mango'];

print(fruits.contains('Banana'));
print(fruits.contains('Orange'));

Output:

true
false

indexOf()

The indexOf() method returns the index of the first matching element.

var fruits = ['Apple', 'Banana', 'Mango'];

print(fruits.indexOf('Mango'));

Output:

2

lastIndexOf()

var numbers = [10, 20, 10, 30];

print(numbers.lastIndexOf(10));

Output:

2

11. Iterating Through a List

Using for Loop

var fruits = ['Apple', 'Banana', 'Mango'];

for (int i = 0; i < fruits.length; i++) {
  print(fruits[i]);
}

Using for-in Loop

var fruits = ['Apple', 'Banana', 'Mango'];

for (var fruit in fruits) {
  print(fruit);
}

Using forEach()

var fruits = ['Apple', 'Banana', 'Mango'];

fruits.forEach((fruit) {
  print(fruit);
});

12. first and last

You can directly access the first and last elements using first and last.

var numbers = [10, 20, 30, 40];

print(numbers.first);
print(numbers.last);

Output:

10
40

13. Sorting a List

Sorting Numbers

var numbers = [50, 10, 40, 20, 30];

numbers.sort();

print(numbers);

Output:

[10, 20, 30, 40, 50]

Sorting in Descending Order

var numbers = [50, 10, 40, 20, 30];

numbers.sort((a, b) => b.compareTo(a));

print(numbers);

Sorting Strings

var names = ['Rahul', 'Amit', 'Zoya', 'Neha'];

names.sort();

print(names);

14. Reversing a List

The reversed property returns the elements in reverse order as an Iterable.

var numbers = [10, 20, 30, 40];

var reversedNumbers = numbers.reversed.toList();

print(reversedNumbers);

Output:

[40, 30, 20, 10]

15. Filtering List Data with where()

The where() method returns elements that satisfy a condition.

var numbers = [10, 15, 20, 25, 30];

var evenNumbers = numbers.where((number) => number % 2 == 0).toList();

print(evenNumbers);

Output:

[10, 20, 30]

Practical Example

var marks = [45, 80, 32, 90, 65];

var passedStudents = marks.where((mark) => mark >= 40).toList();

print(passedStudents);

16. Transforming Lists with map()

The map() method transforms every element into another value.

var numbers = [1, 2, 3, 4, 5];

var squares = numbers.map((number) => number * number).toList();

print(squares);

Output:

[1, 4, 9, 16, 25]

Example with Strings

var names = ['amit', 'rahul', 'neha'];

var upperNames = names.map((name) => name.toUpperCase()).toList();

print(upperNames);

17. any() Method

The any() method checks whether at least one element satisfies a condition.

var numbers = [10, 20, 35, 40];

bool result = numbers.any((number) => number > 30);

print(result);

Output:

true

18. every() Method

The every() method checks whether all elements satisfy a condition.

var marks = [60, 70, 80, 90];

bool result = marks.every((mark) => mark >= 40);

print(result);

Output:

true

19. firstWhere()

firstWhere() returns the first element that satisfies a condition.

var numbers = [10, 15, 22, 35, 40];

var result = numbers.firstWhere((number) => number % 2 == 0);

print(result);

Output:

22

20. take() and skip()

take()

take() returns the first specified number of elements.

var numbers = [10, 20, 30, 40, 50];

var result = numbers.take(3).toList();

print(result);

Output:

[10, 20, 30]

skip()

var numbers = [10, 20, 30, 40, 50];

var result = numbers.skip(2).toList();

print(result);

Output:

[30, 40, 50]

21. sublist()

The sublist() method returns part of a list.

var numbers = [10, 20, 30, 40, 50];

var result = numbers.sublist(1, 4);

print(result);

Output:

[20, 30, 40]

The start index is included, while the end index is excluded.

22. List of Objects

Lists become especially useful when working with custom classes.

class Student {
  String name;
  int marks;

  Student(this.name, this.marks);
}

void main() {
  List students = [
    Student('Amit', 85),
    Student('Neha', 92),
    Student('Rahul', 74),
  ];

  for (var student in students) {
    print('${student.name}: ${student.marks}');
  }
}

This approach is commonly used in Flutter applications when displaying structured data.

23. Filtering a List of Objects

class Student {
  String name;
  int marks;

  Student(this.name, this.marks);
}

void main() {
  List students = [
    Student('Amit', 85),
    Student('Neha', 35),
    Student('Rahul', 74),
  ];

  var passed = students
      .where((student) => student.marks >= 40)
      .toList();

  for (var student in passed) {
    print(student.name);
  }
}

24. List of Maps

Lists can also contain Map objects. This is common when handling JSON-like data.

List> products = [
  {
    'name': 'Laptop',
    'price': 55000
  },
  {
    'name': 'Phone',
    'price': 25000
  },
  {
    'name': 'Tablet',
    'price': 18000
  }
];

print(products[0]['name']);
print(products[1]['price']);

25. Nested Lists

A list can contain other lists.

List> matrix = [
  [1, 2, 3],
  [4, 5, 6],
  [7, 8, 9]
];

print(matrix[0][1]);
print(matrix[2][2]);

Output:

2
9

26. List.generate()

List.generate() creates a list by calling a function for each index.

var numbers = List.generate(
  5,
  (index) => index + 1,
);

print(numbers);

Output:

[1, 2, 3, 4, 5]

Flutter Example

final colors = List.generate(
  10,
  (index) => 'Color $index',
);

27. List.filled()

List.filled() creates a list with a specified number of elements.

var numbers = List.filled(5, 0);

print(numbers);

Output:

[0, 0, 0, 0, 0]

28. Fixed-Length and Growable Lists

Growable List

A normal list literal creates a growable list.

var numbers = [10, 20, 30];

numbers.add(40);

print(numbers);

Fixed-Length List

var numbers = List.filled(3, 0);

numbers[0] = 10;
numbers[1] = 20;
numbers[2] = 30;

print(numbers);

A fixed-length list does not allow operations that change its length, such as add() or remove().

29. final List vs const List

final List

final prevents the variable from referring to a different list, but the contents of a normal growable list can still be changed.

final fruits = ['Apple', 'Banana'];

fruits.add('Mango');

print(fruits);

const List

A const list is compile-time constant and cannot be modified.

const fruits = ['Apple', 'Banana'];

// fruits.add('Mango'); // Error

30. Spread Operator

The spread operator ... inserts elements from another collection into a list.

var first = [1, 2, 3];
var second = [4, 5, 6];

var combined = [...first, ...second];

print(combined);

Output:

[1, 2, 3, 4, 5, 6]

31. Null-Aware Spread Operator

The ...? operator allows a nullable list to be spread without causing an error when the list is null.

List? extraItems;

var items = [
  'Apple',
  ...?extraItems,
  'Mango'
];

print(items);

32. Collection-if

Dart allows conditional elements inside collection literals.

bool isAdmin = true;

var menuItems = [
  'Home',
  'Profile',
  if (isAdmin) 'Admin Panel',
];

print(menuItems);

Output:

[Home, Profile, Admin Panel]

33. Collection-for

A for loop can also be used inside a collection literal.

var numbers = [
  for (var i = 1; i <= 5; i++) i * 10
];

print(numbers);

Output:

[10, 20, 30, 40, 50]

34. Combining Collection-if and Collection-for

bool includeEven = true;

var numbers = [
  for (var i = 1; i <= 10; i++)
    if (!includeEven || i % 2 == 0) i
];

print(numbers);

35. Calculating Values from a List

Using reduce()

var numbers = [10, 20, 30, 40];

var total = numbers.reduce((a, b) => a + b);

print(total);

Output:

100

Using fold()

var numbers = [10, 20, 30, 40];

var total = numbers.fold(0, (sum, number) => sum + number);

print(total);

36. Joining List Elements

The join() method combines list elements into a string.

var names = ['Amit', 'Rahul', 'Neha'];

var result = names.join(', ');

print(result);

Output:

Amit, Rahul, Neha

37. Copying a List

You can create a separate list using List.from() or List.of().

var original = [10, 20, 30];

var copy = List.from(original);

copy.add(40);

print(original);
print(copy);

Output:

[10, 20, 30]
[10, 20, 30, 40]

38. Practical Shopping Cart Example

class Product {
  String name;
  double price;

  Product(this.name, this.price);
}

void main() {
  List cart = [
    Product('Laptop', 55000),
    Product('Mouse', 1200),
    Product('Keyboard', 2500),
  ];

  double total = cart.fold(
    0,
    (sum, product) => sum + product.price,
  );

  print('Cart Items:');

  for (var product in cart) {
    print('${product.name} - ₹${product.price}');
  }

  print('Total: ₹$total');
}

39. Working with Lists in Flutter

Lists are frequently used in Flutter to generate widgets dynamically. Instead of manually writing every widget, you can store data in a list and generate widgets from that data.

Example: Dynamic Text Widgets

import 'package:flutter/material.dart';

class FruitList extends StatelessWidget {
  FruitList({super.key});

  final List fruits = [
    'Apple',
    'Banana',
    'Mango',
    'Orange',
  ];

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(
        title: const Text('Fruits'),
      ),
      body: ListView.builder(
        itemCount: fruits.length,
        itemBuilder: (context, index) {
          return ListTile(
            title: Text(fruits[index]),
          );
        },
      ),
    );
  }
}

40. Updating a List in Flutter

When list data changes inside a StatefulWidget, setState() can be used to rebuild the UI.

class TodoPage extends StatefulWidget {
  const TodoPage({super.key});

  @override
  State createState() => _TodoPageState();
}

class _TodoPageState extends State {
  final List todos = [];

  void addTodo() {
    setState(() {
      todos.add('New Task');
    });
  }

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(
        title: const Text('Todo List'),
      ),
      body: ListView.builder(
        itemCount: todos.length,
        itemBuilder: (context, index) {
          return ListTile(
            title: Text(todos[index]),
          );
        },
      ),
      floatingActionButton: FloatingActionButton(
        onPressed: addTodo,
        child: const Icon(Icons.add),
      ),
    );
  }
}

41. List of Products in Flutter

final products = [
  {
    'name': 'Laptop',
    'price': 55000,
  },
  {
    'name': 'Phone',
    'price': 25000,
  },
  {
    'name': 'Headphones',
    'price': 3000,
  },
];

The data can then be displayed dynamically:

ListView.builder(
  itemCount: products.length,
  itemBuilder: (context, index) {
    final product = products[index];

    return ListTile(
      title: Text(product['name'].toString()),
      subtitle: Text('₹${product['price']}'),
    );
  },
)

42. Common List Methods

Method/PropertyPurpose
lengthReturns the number of elements.
isEmptyChecks whether the list is empty.
isNotEmptyChecks whether the list contains elements.
add()Adds one element.
addAll()Adds multiple elements.
insert()Inserts an element at an index.
insertAll()Inserts multiple elements.
remove()Removes a matching element.
removeAt()Removes an element at an index.
removeLast()Removes the last element.
removeRange()Removes a range of elements.
clear()Removes all elements.
contains()Checks whether an element exists.
indexOf()Finds the first matching index.
sort()Sorts the list.
where()Filters elements.
map()Transforms elements.
any()Checks whether at least one element matches.
every()Checks whether all elements match.
firstWhere()Finds the first matching element.
take()Gets the first specified number of elements.
skip()Skips the first specified number of elements.
sublist()Gets a portion of the list.
join()Combines elements into a string.
fold()Combines elements into a single result.

43. List vs Set vs Map

CollectionStructureDuplicatesAccess
ListOrdered valuesAllowedIndex
SetUnique valuesNot allowedBy value
MapKey-value pairsKeys must be uniqueBy key

44. Common Mistakes

  • Trying to access an index that does not exist.
  • Calling remove() or add() on a fixed-length list.
  • Forgetting to call toList() when a real List is required from an Iterable result such as map(), where(), or reversed.
  • Using dynamic unnecessarily instead of specifying a useful list type.
  • Modifying a list while iterating over it without understanding the consequences.
  • Using a very large static list directly in a Flutter UI instead of an appropriate lazy builder such as ListView.builder.
  • Accessing first or last on an empty list.

45. Best Practices

  • Use generic types such as List and List whenever possible.
  • Use meaningful variable names such as students, products, and cartItems.
  • Use where() for filtering and map() for transformation.
  • Use ListView.builder for large or dynamically generated Flutter lists.
  • Check isNotEmpty before accessing first or last when the list may be empty.
  • Use immutable or unmodifiable collections where mutation is not required.
  • Prefer strongly typed model classes for complex application data instead of deeply nested Map structures.
  • Use collection-if, collection-for, and spread operators to build collections cleanly.

46. Mini Project: Student Marks Management

class Student {
  String name;
  int marks;

  Student(this.name, this.marks);
}

void main() {
  List students = [
    Student('Amit', 85),
    Student('Rahul', 35),
    Student('Neha', 92),
    Student('Priya', 68),
  ];

  print('All Students:');

  for (var student in students) {
    print('${student.name}: ${student.marks}');
  }

  var passedStudents = students
      .where((student) => student.marks >= 40)
      .toList();

  print('\nPassed Students:');

  for (var student in passedStudents) {
    print(student.name);
  }

  var marks = students.map((student) => student.marks).toList();

  var totalMarks = marks.fold(
    0,
    (sum, mark) => sum + mark,
  );

  var average = totalMarks / marks.length;

  print('\nAverage Marks: $average');
}

47. Practice Exercises

  1. Create a list of 10 integers and print all elements.
  2. Find the largest number in a list.
  3. Find the smallest number in a list.
  4. Filter all even numbers from a list.
  5. Filter all numbers greater than 50.
  6. Sort a list in ascending and descending order.
  7. Remove duplicate values from a collection using a Set and convert it back to a List.
  8. Create a list of student objects and display students who scored more than 75.
  9. Create a shopping cart using a list of Product objects and calculate the total price.
  10. Display a list of products dynamically using Flutter's ListView.builder.

48. Quick Revision

  • List: Ordered collection of values.
  • Index: Position of an element, starting from 0.
  • length: Number of elements.
  • add(): Adds one element.
  • addAll(): Adds multiple elements.
  • remove(): Removes a matching element.
  • removeAt(): Removes an element by index.
  • where(): Filters elements.
  • map(): Transforms elements.
  • sort(): Sorts elements.
  • contains(): Checks whether an element exists.
  • for-in: Iterates through elements.
  • List.generate(): Generates a list programmatically.
  • ...: Spread operator.
  • ...?: Null-aware spread operator.
  • ListView.builder: Efficiently builds dynamic Flutter list UIs.

49. Conclusion

Working with Lists is an essential Dart skill for Flutter development. Lists allow developers to store, access, update, filter, sort, transform, and display collections of data efficiently. Once you understand list operations such as add(), remove(), where(), map(), sort(), collection operators, and list iteration, you can build dynamic Flutter interfaces that work with real application data.

Official Dart Resources

Learn Flutter with JustAcademy

whatsapp